package com.tmptSource.service.impl;

import com.tmpt.dto.Result;
import com.tmpt.utils.DateTool;
import com.tmpt.service.impl.DataLimitService;
import com.tmpt.utils.StringUtils;
import com.tmpt.utils.location.LocationUtils;
import com.tmptSource.bean.*;
import com.tmptSource.dto.OwPictureMagDto;
import com.tmptSource.mapper.*;
import com.tmptSource.dto.OwSigninDto;
import com.tmptSource.dto.PageDto;
import com.tmptSource.service.intf.IOwSigninService;
import org.apache.log4j.Logger;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import com.tmptSource.utils.dozer.MyMapper;
import com.tmptSource.utils.page.MyPageUtils;

import java.sql.Timestamp;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.HashMap;
import org.dozer.Mapper;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

/**
 * Created by wxy on 2016/7/28.
 */
@Service(value="owSigninService")
@Transactional(propagation = Propagation.REQUIRED)
public class OwSigninService implements IOwSigninService {

    private Logger log = Logger.getLogger(this.getClass());
    @Autowired private DataLimitService dataLimitService;
    @Autowired private Mapper mapper;
    @Autowired private MyMapper myMapper;
    @Autowired private MyPageUtils myPageUtils;
    @Autowired
    private OwSigninMapper owSigninMapper;
    @Autowired
    private OwPictureMagMapper owPictureMagMapper;
    @Autowired
    private OwWorkPlanMapper owWorkPlanMapper;
    @Autowired
    private OwSignAddressMapper owSignAddressMapper;
    @Autowired
    private OwUserTrackMapper owUserTrackMapper;


    @Override
    public Result<OwSigninDto> pagination(OwSigninDto owSigninDto,PageDto pageDto) {
        //分页查询
        Result<OwSigninDto> result = myPageUtils.pagination(
                owSigninDto, pageDto,
                OwSignin.class,
                OwSigninDto.class,
                owSigninMapper,
                false, null);

        return result;
    }

    /**
    * 分布查询，有数据边界控制功能
    * @param owSigninDto
    * @param pageDto
    * @param paramMap
    * @return
    */
    @Override
    public Result<OwSigninDto> pagination(OwSigninDto owSigninDto,PageDto pageDto,Map<String,Object> paramMap) {
        //数据边界控制参数
        Map<String,Object> paramMap1 = dataLimitService.getLimitParam(paramMap);

        //分页查询
        Result<OwSigninDto> result = myPageUtils.pagination(
                owSigninDto, pageDto,
                OwSignin.class,
                OwSigninDto.class,
                owSigninMapper,
                paramMap1,
                false, null);

        return result;
    }


    @Override
    public Result<OwSigninDto> selectAll() {
        Result<OwSigninDto> result = new Result();

        //排序
        PageDto pageDto = new PageDto();
        pageDto.setSortColumn("id");
        pageDto.setSortOrder("desc");
        Map<String,Object> mapParam = new HashMap<>();
        mapParam.put("page",pageDto);

        List<OwSignin> list = owSigninMapper.selectAll(mapParam);
        List<OwSigninDto> dtoList = myMapper.map(list, OwSigninDto.class);
        result.setResultList(dtoList);

        return result.success();
    }

    @Override
    public Result<OwSigninDto> selectById(long id) {
        Result<OwSigninDto> result = new Result();

        OwSignin owSignin = owSigninMapper.selectById(id);
        OwSigninDto dto = mapper.map(owSignin, OwSigninDto.class);
        result.setResultObj(dto);

        return result.success();
    }


    /**
        返回ID值
    */
    @Override
    public Result<OwSigninDto> addData(OwSigninDto owSigninDto){
        Result<OwSigninDto> result = new Result();

        //封闭数据
        OwSignin owSignin = mapper.map(owSigninDto, OwSignin.class);
        owSignin.setCreatedate(DateTool.getCurTimestamp());

        //调用mapper
        long i = owSigninMapper.insert(owSignin);
        if(i==0){
            return result.fault("插入失败");
        }

        //插入签到点轨迹
        OwUserTrack owUserTrack = new OwUserTrack();
        owUserTrack.setA2userId(Integer.parseInt(owSignin.getA2userId().toString()));
        owUserTrack.setLat(owSignin.getLat());
        owUserTrack.setLng(owSignin.getLng());
        owUserTrack.setCreatedate(owSignin.getCreatedate());
        owUserTrack.setCreateman(owSignin.getCreateman());
        owUserTrack.setCreatemanId(owSignin.getCreatemanId());
        owUserTrack.setCompanyId(owSignin.getCompanyId());
        owUserTrackMapper.insert(owUserTrack);

        //插入多张图片
        if(owSigninDto!=null && owSigninDto.getOwPictureMagDtoList()!=null) {
            for (OwPictureMagDto owPictureMagDto : owSigninDto.getOwPictureMagDtoList()) {
                OwPictureMag owPictureMag = mapper.map(owPictureMagDto, OwPictureMag.class);
                //1:front, 2:back （默认设1）
                owPictureMag.setFrontBackSort(
                        StringUtils.isNull(owPictureMagDto.getFrontBackSort())?1:Integer.parseInt(owPictureMagDto.getFrontBackSort()));
                owPictureMag.setOwTableType("ow_signin_id");
                owPictureMag.setOwTableId(owSignin.getId());
                owPictureMag.setCompanyId(0);
                owPictureMag.setCreatemanId(0);
                owPictureMag.setModifymanId(0);
                owPictureMagMapper.insert(owPictureMag);
            }
        }

        OwSigninDto dto = mapper.map(owSignin, OwSigninDto.class);
        result.setResultObj(dto);

        return result.success();
    }


    /**
     * 用户签到
     * @param owSigninDto
     * @return
     */
    @Override
    public Result<OwSigninDto> checkAndAddSignin(OwSigninDto owSigninDto){
        Result<OwSigninDto> result = new Result();
        String curLng = owSigninDto.getLng();
        String curLat = owSigninDto.getLat();

        //根据排班计划，查询用户所属区域下的签到点列表
        String userId = owSigninDto.getA2userId();
        if(StringUtils.isNull(userId)){return result.fault("请重新登录");}
        int userIdInt = Integer.parseInt(userId);
        //根据排班计划查询用户当前时间负责哪个区域
        Result<OwWorkPlan> resultArea = queryWorkPlanByUser(userIdInt);
        if(!resultArea.isSuccess()){return result.fault(resultArea.getContent());}
        //用户负责多区域时，把签到点整理出来
        List<OwSignAddress> owSignAddressList = querySigninAddressByWordplan(resultArea.getResultList())
                .getResultList();
        //判断用户的经纬度，在不在这些签到点里，获取当前签到点
        OwSignAddress owSignAddress = queryMyCurSignAddress(owSignAddressList,curLng,curLat).getResultObj();
        if(owSignAddress == null){
            return result.fault("未在签到点内");
        }
        //用户在签到点里，取签到点签到模式
        int signMode = owSignAddress.getSignMode();
        //mode=1,直接签到成功
        if(signMode == 1){
            Result result1 = addData(owSigninDto);
            result1.getResultMap().put("signMode",signMode);
            result1.getResultMap().put("owSignAddressName",owSignAddress.getName());
            return result1;
        }
        //mode=2,用户拍照上传进行签到成功
        if(signMode == 2){
            result.getResultMap().put("signMode",signMode);
            result.getResultMap().put("owSignAddressName",owSignAddress.getName());
        }

        return result.success();
    }

    /**
     * 判断用户的经纬度，在不在这些签到点里，获取当前签到点
     * @param owSignAddressList
     * @param curLng
     * @param curLat
     * @return
     */
    private Result<OwSignAddress> queryMyCurSignAddress(List<OwSignAddress> owSignAddressList,String curLng,String curLat){
        Result<OwSignAddress> result = new Result();

        for(OwSignAddress owSignAddress : owSignAddressList){
            String lng = owSignAddress.getLng();
            String lat = owSignAddress.getLat();
            String radius = owSignAddress.getRadius();
            Double radiusDouble = Double.parseDouble(radius);
            double distance = LocationUtils.getDistance(Double.parseDouble(lat),Double.parseDouble(lng),
                    Double.parseDouble(curLat),Double.parseDouble(curLng));
            if(distance<radiusDouble){
                result.setResultObj(owSignAddress);
                break;
            }
        }

        return result.success();
    }

    /**
     * 用户负责多区域时，把签到点整理出来
     * @param owWorkPlanList
     * @return
     */
    private Result<OwSignAddress> querySigninAddressByWordplan(List<OwWorkPlan> owWorkPlanList){
        Result<OwSignAddress> result = new Result();

        for(OwWorkPlan owWorkPlan : owWorkPlanList){
            long owAreaId = owWorkPlan.getOwAreaId();
            OwSignAddress owSignAddress = new OwSignAddress();
            owSignAddress.setOwAreaId(owAreaId);
            Map<String,Object> mapParam = new HashMap<>();
            mapParam.put("bean", owSignAddress);
            List<OwSignAddress> owSignAddressList = owSignAddressMapper.selectAll(mapParam);
            result.getResultList().addAll(owSignAddressList);
        }

        return result.success();
    }

    /**
     * 根据排班计划查询用户当前时间负责哪个区域
     * @param userIdInt
     * @return
     */
    private Result<OwWorkPlan> queryWorkPlanByUser(int userIdInt){
        Result<OwWorkPlan> result = new Result();

        OwWorkPlan owWorkPlan = new OwWorkPlan();
        owWorkPlan.setA2userId(userIdInt);
        Map<String,Object> mapParam = new HashMap<>();
        mapParam.put("bean", owWorkPlan);
        List<OwWorkPlan> owWorkPlanListTmp = owWorkPlanMapper.selectAll(mapParam);
        for(OwWorkPlan owWorkPlan1 : owWorkPlanListTmp){
            Timestamp startTime = owWorkPlan1.getStartTime();
            Timestamp endTime = owWorkPlan1.getEndTime();
            Timestamp currentTime = DateTool.getCurTimestamp();
            if(currentTime.after(startTime) && currentTime.before(endTime)){
                result.getResultList().add(owWorkPlan1);
            }
        }
        if(result.getResultList().isEmpty()){
            return result.fault("当前用户无排班计划");
        }
        /*if(result.getResultList().size()>1){
            return result.fault("用户排班设置有误，当前用户设置成负责多区域了");
        }*/

        return result.success();
    }


    /**
        返回ID值
    */
    @Override
    public Result<OwSigninDto> editData(OwSigninDto owSigninDto){
        Result<OwSigninDto> result = new Result();

        //封装数据
        OwSignin owSignin = mapper.map(owSigninDto, OwSignin.class);
        owSignin.setModifydate(DateTool.getCurTimestamp());

        //调用mapper
        long i = owSigninMapper.updateById(owSignin);
        if(i==0){
            return result.fault("编辑数据失败");
        }

        OwSigninDto dto = mapper.map(owSignin,OwSigninDto.class);
        result.setResultObj(dto);

        return result.success();
    }

    /**
    伪删除记录，返回ID值
    */
    @Override
    public Result deleteById(long id,String adminMan){
        Result result = new Result();

        Map<String,Object> mapParameter = new HashMap();
        mapParameter.put("id",id);
        mapParameter.put("modifyman",adminMan);
        mapParameter.put("modifydate",DateTool.getCurTimestamp());

        //调用mapper
        long i = owSigninMapper.deleteById(mapParameter);
        if(i==0){
            return result.fault("删除数据失败");
        }

        return result.success();
    }




    /**
    *页面上查询列的值，动态加载，sql语句读数据库配置而来
    */
    public java.util.List select4a2userId(){
        return owSigninMapper.select4a2userId();
    }
    /**
    *页面上查询列的值，动态加载，sql语句读数据库配置而来
    */
    public java.util.List select4owSignAddressId(){
        return owSigninMapper.select4owSignAddressId();
    }

}
